//
//  SYTimeManager.h
//  Lefant
//
//  Created by sy on 2021/11/18.
//
#import "SYTimeManager.h"

#define KTampWeek @[ @"周日", @"周一", @"周二", @"周三", @"周四", @"周五", @"周六" ]

@implementation SYTimeManager

#pragma mark -
#pragma mark - 获取 [ 年、月、日、周 ] 数组
+ (NSArray*)timeOFDate:(NSDate*)date {
    NSDateComponents* components = [[NSCalendar currentCalendar]
        components:NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay |
                   NSCalendarUnitWeekday
          fromDate:date ?: [NSDate date]];

    NSString* yearStr =
        [NSString stringWithFormat:@"%ld", (long)[components year]];
    NSString* monthStr =
        [NSString stringWithFormat:@"%.2ld", (long)[components month]];
    NSString* dayStr =
        [NSString stringWithFormat:@"%.2ld", (long)[components day]];
    NSString* weekStr =
        [NSString stringWithFormat:@"%ld", (long)[components weekday] - 1];

    return [NSArray arrayWithObjects:yearStr, monthStr, dayStr, weekStr, nil];
}
+ (NSArray*)timeOFDateAllTime:(NSDate*)date {
    NSDateComponents* components = [[NSCalendar currentCalendar] components:
                                                                     NSCalendarUnitYear |
                                                                     NSCalendarUnitMonth |
                                                                     NSCalendarUnitDay |
                                                                     NSCalendarUnitHour |
                                                                     NSCalendarUnitMinute |
                                                                     NSCalendarUnitSecond
                                                                   fromDate:date ?: [NSDate date]];

    NSString* yearStr =
        [NSString stringWithFormat:@"%ld", (long)[components year]];
    NSString* monthStr =
        [NSString stringWithFormat:@"%.2ld", (long)[components month]];
    NSString* dayStr =
        [NSString stringWithFormat:@"%.2ld", (long)[components day]];

    NSString* hourStr =
        [NSString stringWithFormat:@"%.2ld", (long)[components hour]];
    NSString* minuteStr =
        [NSString stringWithFormat:@"%.2ld", (long)[components minute]];
    NSString* secondStr =
        [NSString stringWithFormat:@"%.2ld", (long)[components second]];

    return [NSArray arrayWithObjects:yearStr, monthStr, dayStr, hourStr, minuteStr, secondStr, nil];
}
#pragma mark -
#pragma mark - 获取 [ 本年初、末 ] 数组
+ (NSArray*)timeOFStartAndEndForYear:(NSDate*)date {
    NSArray* timeArray = [self timeOFDate:date];

    NSString* startTime =
        [NSString stringWithFormat:@"%@年01月01日", timeArray[0]];
    NSString* endTime =
        [NSString stringWithFormat:@"%@年12月31日", timeArray[0]];

    return [NSArray arrayWithObjects:startTime, endTime, nil];
}

#pragma mark -
#pragma mark - 获取 [ 本月初、末 ] 数组
+ (NSArray*)timeOFStartAndEndForMonth:(NSDate*)date {
    NSArray* timeArray = [self timeOFDate:date];

    NSCalendar* calendar = [[NSCalendar alloc]
        initWithCalendarIdentifier:NSCalendarIdentifierGregorian];
    NSRange range = [calendar rangeOfUnit:NSCalendarUnitDay
                                   inUnit:NSCalendarUnitMonth
                                  forDate:date];
    NSUInteger numberOfDaysInMonth = range.length;

    NSDateComponents* components = [[NSCalendar currentCalendar]
        components:NSCalendarUnitDay
          fromDate:date ?: [NSDate date]];

    NSString* dayStr = [NSString stringWithFormat:@"%02ld", (long)[components day]];

    NSString* startTime = [NSString
        stringWithFormat:@"%@%@01", timeArray[0], timeArray[1]];
    NSString* endTime = [NSString
        stringWithFormat:@"%@%@%@", timeArray[0], timeArray[1], [dayStr integerValue] <= numberOfDaysInMonth ? dayStr : [NSString stringWithFormat:@"%02ld", numberOfDaysInMonth]];

    return [NSArray arrayWithObjects:startTime, endTime, nil];
}

#pragma mark -
#pragma mark - 获取 [ 本日初、末 ] 数组
+ (NSArray*)timeOFStartAndEndForDay:(NSDate*)date {
    NSArray* timeArray = [self timeOFDate:date];

    NSString* startTime =
        [NSString stringWithFormat:@"%@年%@月%@日", timeArray[0],
                                   timeArray[1], timeArray[2]];
    NSString* endTime =
        [NSString stringWithFormat:@"%@年%@月%@日", timeArray[0],
                                   timeArray[1], timeArray[2]];

    return [NSArray arrayWithObjects:startTime, endTime, nil];
}

#pragma mark -
#pragma mark - 获取 [ 本周初、末 ] 数组
+ (NSArray*)timeOFStartAndEndForWeek:(NSDate*)date {
    NSDate* nowDate = (date ? date : [NSDate date]);
    NSCalendar* calendar = [NSCalendar currentCalendar];

    NSDateComponents* comp =
        [calendar components:NSCalendarUnitYear | NSCalendarUnitMonth |
                             NSCalendarUnitDay | NSCalendarUnitWeekday
                    fromDate:nowDate];

    // 获取今天是周几
    NSInteger weekDay = [comp weekday];

    /**获取当前几个月*/
    NSInteger monthDay = [comp month];

    //    UMLog(@"%ld", monthDay);

    // 获取几天是几号
    NSInteger day = [comp day];
    //    UMLog(@"%ld----%ld", weekDay, day);

    // 计算当前日期和本周的星期一和星期天相差天数
    long firstDiff, lastDiff;

    //    weekDay = 1;

    if (weekDay == 1) {
        firstDiff = -6;
        lastDiff = 0;

    } else {
        firstDiff = [calendar firstWeekday] - weekDay + 1;
        lastDiff = 8 - weekDay;
    }

    //    UMLog(@"firstDiff: %ld   lastDiff: %ld", firstDiff, lastDiff);

    // 在当前日期(去掉时分秒)基础上加上差的天数
    NSDateComponents* firstDayComp = [calendar
        components:NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay
          fromDate:nowDate];

    [firstDayComp setDay:day + firstDiff];
    NSDate* firstDayOfWeek = [calendar dateFromComponents:firstDayComp];

    NSDateComponents* lastDayComp = [calendar
        components:NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay
          fromDate:nowDate];

    [lastDayComp setDay:day + lastDiff];

    NSDate* lastDayOfWeek = [calendar dateFromComponents:lastDayComp];
    if ([lastDayOfWeek compare:[NSDate date]] == NSOrderedDescending) {
        lastDayOfWeek = [NSDate date];
    }

    NSDateFormatter* formatter = [[NSDateFormatter alloc] init];
    formatter.locale = [NSLocale systemLocale];
    formatter.calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierISO8601];

    [formatter setDateFormat:@"yyyyMMdd"];

    NSString* firstDay = [formatter stringFromDate:firstDayOfWeek];
    NSString* lastDay = [formatter stringFromDate:lastDayOfWeek];

    return [NSArray arrayWithObjects:firstDay, lastDay, nil];
}

#pragma mark -
#pragma mark - 获取 [ 周一、今天 ] 数组
+ (NSArray*)timeOFMondayToToday:(NSDate*)date {
    NSArray* timeArray = [self timeOFDate:date];

    NSInteger weekday = [timeArray[3] integerValue];

    return [self timeOFOtherDayToToday:weekday - 1];
}

#pragma mark -
#pragma mark - 获取 [ N天前、今天 ] 数组
+ (NSArray*)timeOFOtherDayToToday:(NSInteger)count {
    NSInteger timeInterval = (count - 1) * 24 * 60 * 60;
    NSTimeInterval now = [[NSDate date] timeIntervalSince1970];
    NSInteger newTime = now - timeInterval;
    NSDate* newDate = [NSDate dateWithTimeIntervalSince1970:newTime];

    NSDateFormatter* formatter = [[NSDateFormatter alloc] init];
    formatter.locale = [NSLocale systemLocale];
    formatter.calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierISO8601];

    [formatter setDateFormat:@"yyyy年MM月dd日"];
    NSString* beforeDateStr = [formatter stringFromDate:newDate];

    NSString* dateStr = [formatter stringFromDate:[NSDate date]];

    return [NSArray arrayWithObjects:beforeDateStr, dateStr, nil];
}

#pragma mark -
#pragma mark - 获取 [ 今天、N天后 ] 数组
+ (NSArray*)timeOFTodayToOtherDay:(NSInteger)count {
    NSInteger timeInterval = (count + 1) * 24 * 60 * 60;
    NSTimeInterval now = [[NSDate date] timeIntervalSince1970];
    NSInteger newTime = now + timeInterval;
    NSDate* newDate = [NSDate dateWithTimeIntervalSince1970:newTime];

    NSDateFormatter* formatter = [[NSDateFormatter alloc] init];
    formatter.locale = [NSLocale systemLocale];
    formatter.calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierISO8601];

    [formatter setDateFormat:@"yyyy年MM月dd日"];
    NSString* beforeDateStr = [formatter stringFromDate:newDate];

    NSString* dateStr = [formatter stringFromDate:[NSDate date]];

    return [NSArray arrayWithObjects:beforeDateStr, dateStr, nil];
}
#pragma mark -
#pragma mark - 获取 [ 初始、结束(时间戳) ] 数组
+ (NSArray*)timeStampOFStartAndEnd:(NSArray*)timeArray {
    NSString* begainTime =
        [NSString stringWithFormat:@"%@ 00:00:00", timeArray[0]];
    NSString* endTime = [NSString stringWithFormat:@"%@ 23:59:59", timeArray[1]];

    //    UMLog(@"start:%@___end:%@",begainTime,endTime);

    NSDateFormatter* dateFormatter = [[NSDateFormatter alloc] init];
    dateFormatter.locale = [NSLocale systemLocale];
    dateFormatter.calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierISO8601];

    [dateFormatter setDateFormat:@"yyyy年MM月dd日 HH:mm:ss"];

    NSDate* begainDate = [dateFormatter dateFromString:begainTime];
    NSString* filterOfTimeBegain = [NSString
        stringWithFormat:@"%ld", (long)[begainDate timeIntervalSince1970] * 1000];
    NSDate* endDate = [dateFormatter dateFromString:endTime];
    NSString* filterOfTimeEnd =
        [NSString stringWithFormat:@"%ld", (long)[endDate timeIntervalSince1970] * 1000];
    //    UMLog(@"start:%@___end:%@",filterOfTimeBegain,filterOfTimeEnd);

    return [NSArray arrayWithObjects:filterOfTimeBegain, filterOfTimeEnd, nil];
}

- (void)getQuarterBeginAndEndWith:(NSDate*)currentDate {
    NSDate* nowDate = [NSDate date];

    NSCalendar* calendar = [NSCalendar currentCalendar];

    NSDateComponents* comp =
        [calendar components:NSCalendarUnitYear | NSCalendarUnitMonth |
                             NSCalendarUnitDay | NSCalendarUnitWeekday
                    fromDate:nowDate];

    /**获取当前的月份*/

    NSInteger curentMonth = [comp month];
    NSString* currentYear = [NSString stringWithFormat:@"%ld", [comp year]];

    NSString* beginTime =
        [self getQuarterStartDateWithYear:currentYear
                             currentMonth:curentMonth];

    NSString* endTime =
        [self getQuarterEndDateWithYear:currentYear
                           currentMonth:curentMonth];

    NSString* str =
        [NSString stringWithFormat:@"季度开始时间 == %@  季度结束时间 == %@",
                                   beginTime, endTime];

    //    UMLog(@"%@", str);
}

// 获得某季度的开始日期
- (NSString*)getQuarterStartDateWithYear:(NSString*)paraYear
                            currentMonth:(NSInteger)currentMonth {
    NSString* beginTime = @"";

    if (currentMonth < 4) {
        beginTime = [paraYear stringByAppendingString:@"-01-01"];

    } else if (currentMonth >= 4 && currentMonth < 7) {
        beginTime = [paraYear stringByAppendingString:@"-04-01"];

    } else if (currentMonth >= 7 && currentMonth < 10) {
        beginTime = [paraYear stringByAppendingString:@"-07-01"];

    } else if (currentMonth >= 10 && currentMonth < 12) {
        beginTime = [paraYear stringByAppendingString:@"-10-01"];
    }

    return beginTime;
}

// 获得某季度的结束日期
- (NSString*)getQuarterEndDateWithYear:(NSString*)paraYear
                          currentMonth:(NSInteger)currentMonth {
    NSString* endTime = @"";

    if (currentMonth < 4) {
        endTime = [paraYear stringByAppendingString:@"-03-31"];

    } else if (currentMonth >= 4 && currentMonth < 7) {
        endTime = [paraYear stringByAppendingString:@"-06-30"];

    } else if (currentMonth >= 7 && currentMonth < 10) {
        endTime = [paraYear stringByAppendingString:@"-09-30"];

    } else if (currentMonth >= 10 && currentMonth < 12) {
        endTime = [paraYear stringByAppendingString:@"-12-31"];
    }

    return endTime;
}

+ (NSDate*)priousorLaterDateFromDate:(NSDate*)date withDay:(NSInteger)dayCount withMonth:(NSInteger)monthCount andYear:(NSInteger)yearCount {
    // 得到当前的时间
    NSDate* mydate = date ? date : [NSDate date];

    NSCalendar* calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierGregorian];
    NSDateComponents* comps = nil;
    comps = [calendar components:NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitMonth fromDate:mydate];
    NSDateComponents* adcomps = [[NSDateComponents alloc] init];

    [adcomps setYear:yearCount];
    [adcomps setMonth:monthCount];
    [adcomps setDay:dayCount];

    return [calendar dateByAddingComponents:adcomps toDate:mydate options:0];
}
+ (NSComparisonResult)sameWithExpireTime:(NSDate*)expireDate InTargetTime:(NSDate*)date {
    date = date ? date : [NSDate date];
    return [date compare:expireDate];
}

+ (NSString*)currentTimeStr:(NSString*)dateFormatStr WithDate:(NSDate*)date {
    NSDate* today = (date ? date : [NSDate date]);
    NSDateFormatter* dateFormat = [[NSDateFormatter alloc] init];
    dateFormat.locale = [NSLocale systemLocale];
    dateFormat.calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierISO8601];

    [dateFormat setDateFormat:(dateFormatStr.length > 0 ? dateFormatStr : @"yyyy-MM-dd HH:mm")];
    return [dateFormat stringFromDate:today];
}

+ (NSDate*)currentDate:(NSString*)dateFormatStr WithDateStr:(NSString*)dateStr {
    NSDateFormatter* dateFormat = [[NSDateFormatter alloc] init];
    dateFormat.locale = [NSLocale systemLocale];
    dateFormat.calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierISO8601];

    [dateFormat setDateFormat:(dateFormatStr.length > 0 ? dateFormatStr : @"yyyy-MM-dd HH:mm")];

    return [dateFormat dateFromString:dateStr];
}

+ (NSInteger)componentsCalendarUnit:(NSCalendarUnit)unit withStartDate:(NSString*)startTime endDate:(NSString*)entTime {
    NSDateFormatter* formatter = [[NSDateFormatter alloc] init];
    formatter.locale = [NSLocale systemLocale];
    formatter.calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierISO8601];

    [formatter setDateFormat:@"yyyyMMdd"];

    NSDate* start_Date = [formatter dateFromString:startTime];
    NSDate* end_Date = [formatter dateFromString:entTime];

    NSCalendar* calendar = [NSCalendar currentCalendar];

    NSDateComponents* result = [calendar components:unit fromDate:start_Date toDate:end_Date options:0];

    return result.day;
}

/**
 anyDate 转成 本地时区的 NSDate
 */
+ (NSDate*)getLocalDateFormatAnyDate:(NSDate*)anyDate {
    NSTimeZone* sourceTimeZone = [NSTimeZone timeZoneWithAbbreviation:@"UTC"];    // 或GMT
    NSTimeZone* desTimeZone = [NSTimeZone localTimeZone];
    // 得到源日期与世界标准时间的偏移量
    NSInteger sourceGMTOffset = [sourceTimeZone secondsFromGMTForDate:anyDate];
    // 目标日期与本地时区的偏移量
    NSInteger destinationGMTOffset = [desTimeZone secondsFromGMTForDate:anyDate];
    // 得到时间偏移量的差值
    NSTimeInterval interval = destinationGMTOffset - sourceGMTOffset;
    // 转为现在时间
    NSDate* destinationDateNow = [[NSDate alloc] initWithTimeInterval:interval sinceDate:anyDate];
    return destinationDateNow;
}

+ (NSString*)getLocalDateFormatAnyDateStr:(NSString*)anyDateStr withFormate:(NSString*)formateStr {
    /**
     零时区+夏令时
     NSDateFormatter *format = [self createDateForMatter];
     format.dateFormat = @"yyyy-MM-dd HH:mm:ss";
     format.timeZone = [NSTimeZone timeZoneWithName:@"UTC"];
     NSDate *utcDate = [format dateFromString:anyDateStr];

     NSTimeZone *localZone = [NSTimeZone localTimeZone];
     NSTimeInterval timeInterval = [utcDate timeIntervalSince1970];
     if (localZone.daylightSavingTime==YES) {
         timeInterval = timeInterval+localZone.daylightSavingTimeOffset;
     }
     utcDate = [NSDate dateWithTimeIntervalSince1970:timeInterval];

     return [self currentTimeStr:formateStr?:@"yyyy-MM-dd HH:mm:ss" WithDate:utcDate];

     */
    NSDateFormatter* format = [self createDateForMatter];
    format.dateFormat = formateStr ?: @"yyyy-MM-dd HH:mm:ss";
    NSDate* dateFormatted = [format dateFromString:anyDateStr];

    NSTimeZone* localZone = [NSTimeZone localTimeZone];
    NSTimeInterval timeInterval = [dateFormatted timeIntervalSince1970];
    if (localZone.daylightSavingTime == YES) {
        timeInterval = timeInterval + localZone.daylightSavingTimeOffset;
    }
    dateFormatted = [NSDate dateWithTimeIntervalSince1970:timeInterval];

    NSString* dateString = [format stringFromDate:dateFormatted];

    return dateString;
}
/**
 将本地日期字符串转为UTC日期字符串
 eg: 2017-10-25 02:07:39 -> 2017-10-24 18:07:39
 */
+ (NSString*)getUTCStrFormateLocalStr:(NSString*)localStr {
    NSDateFormatter* format = [self createDateForMatter];
    format.dateFormat = @"yyyy-MM-dd HH:mm";
    NSDate* dateFormatted = [format dateFromString:localStr];

    NSTimeZone* localZone = [NSTimeZone localTimeZone];
    NSTimeInterval timeInterval = [dateFormatted timeIntervalSince1970];
    if (localZone.daylightSavingTime == YES) {
        timeInterval = timeInterval - localZone.daylightSavingTimeOffset;
    }
    dateFormatted = [NSDate dateWithTimeIntervalSince1970:timeInterval];

    format.timeZone = [NSTimeZone timeZoneWithName:@"UTC"];
    format.dateFormat = @"yyyy-MM-dd'T'HH:mm:ss.SSS";
    NSString* dateString = [NSString stringWithFormat:@"%@Z", [format stringFromDate:dateFormatted]];
    return dateString;
}

+ (NSString*)getUTCStrHHmmLocalStr:(NSString*)localStr withFormate:(NSString*)formateStr {
    NSDateFormatter* format = [self createDateForMatter];
    format.dateFormat = formateStr ?: @"HH:mm";
    NSDate* date_local = [format dateFromString:localStr];

    NSTimeZone* localZone = [NSTimeZone localTimeZone];
    NSTimeInterval timeInterval = [date_local timeIntervalSince1970];
    if (localZone.daylightSavingTime == YES) {
        timeInterval = timeInterval - localZone.daylightSavingTimeOffset;
    }
    date_local = [NSDate dateWithTimeIntervalSince1970:timeInterval];

    format.timeZone = [NSTimeZone timeZoneWithName:@"UTC"];
    format.dateFormat = formateStr ?: @"HH:mm";
    NSString* dateString = [NSString stringWithFormat:@"%@", [format stringFromDate:date_local]];
    return dateString;
}

/**
 将UTC日期字符串转为本地时间字符串
 eg: 2017-10-25 02:07:39  -> 2017-10-25 10:07:39
 */
+ (NSString*)getLocalDateFormate:(NSString*)dateFormatStr withUTCDate:(NSString*)utcStr {
    NSDateFormatter* format = [self createDateForMatter];
    //        .SSSZZZ
    format.dateFormat = @"yyyy-MM-dd'T'HH:mm:ss.SSSZ";
    format.timeZone = [NSTimeZone timeZoneWithName:@"UTC"];
    NSDate* utcDate = [format dateFromString:utcStr];

    NSTimeZone* localZone = [NSTimeZone localTimeZone];
    NSTimeInterval timeInterval = [utcDate timeIntervalSince1970];
    if (localZone.daylightSavingTime == YES) {
        timeInterval = timeInterval + localZone.daylightSavingTimeOffset;
    }
    utcDate = [NSDate dateWithTimeIntervalSince1970:timeInterval];

    return [self currentTimeStr:dateFormatStr ?: @"yyyy-MM-dd HH:mm" WithDate:utcDate];
}

+ (NSString*)getLocalDateHHMMFormateinUTCDate:(NSString*)utcStr {
    NSDateFormatter* format = [self createDateForMatter];
    format.dateFormat = @"HH:mm";
    format.timeZone = [NSTimeZone timeZoneWithName:@"UTC"];
    NSDate* utcDate = [format dateFromString:utcStr];

    NSTimeZone* localZone = [NSTimeZone localTimeZone];
    NSTimeInterval timeInterval = [utcDate timeIntervalSince1970];
    if (localZone.daylightSavingTime == YES) {
        timeInterval = timeInterval + localZone.daylightSavingTimeOffset;
    }
    utcDate = [NSDate dateWithTimeIntervalSince1970:timeInterval];

    return [self currentTimeStr:@"HH:mm" WithDate:utcDate];
}

+ (BOOL)savedTimeCompareNowIsSameDay:(NSDate*)end_Time {
    return [self TimeCompareIsSameDay:end_Time andTimeTwo:[NSDate date]];
}

+ (BOOL)TimeCompareIsSameDay:(NSDate*)timeOne andTimeTwo:(NSDate*)timeTwo {
    NSCalendar* calendar = [NSCalendar currentCalendar];
    unsigned unitFlags = NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay;
    NSDateComponents* comp1 = [calendar components:unitFlags fromDate:timeOne];
    NSDateComponents* comp2 = [calendar components:unitFlags fromDate:timeTwo];

    return ([comp1 day] == [comp2 day] && [comp1 month] == [comp2 month] && [comp1 year] == [comp2 year]);
}

+ (NSDateFormatter*)createDateForMatter {
    NSDateFormatter* formatter = [[NSDateFormatter alloc] init];
    formatter.locale = [NSLocale systemLocale];
    formatter.calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierISO8601];

    return formatter;
}
@end
